﻿using System;
using System.Threading;

namespace Microsoft.Practices.CompositeUI.Utility
{
    ///<summary>
    ///	Helper class that makes it easier to ensure proper usage of a <see cref = "ReaderWriterLock" /> 
    ///	for readers by providing support for <see cref = "IDisposable" /> and the using keyword.
    ///</summary>
    ///<example>
    ///	Common usage is as follows:
    ///	<code>
    ///		ReaderWriterLock mylock = new ReaderWriterLock();
    /// 
    ///		// Inside some method
    ///		using (new ReaderLock(readerWriterLock))
    ///		{
    ///		// Do your safe resource read accesses here.
    ///		}
    ///	</code>
    ///	If a timeout is specified, the <see cref = "LockBase.TimedOut" /> property should be checked inside the 
    ///	using statement:
    ///	<code>
    ///		ReaderWriterLock mylock = new ReaderWriterLock();
    /// 
    ///		// Inside some method
    ///		using (ReaderLock l = new ReaderLock(readerWriterLock, 100))
    ///		{
    ///		if (l.TimedOut == false)
    ///		{
    ///		// Do your safe resource read accesses here.
    ///		}
    ///		else
    ///		{
    ///		throw new InvalidOperationException("Could not lock the resource.");
    ///		}
    ///		}
    ///	</code>
    ///</example>
    public class ReaderLock : LockBase
    {
        #region Constructors

        /// <summary>
        /// 	Acquires a reader lock on the readerWriterLock received 
        /// 	with no timeout specified.
        /// </summary>
        public ReaderLock(ReaderWriterLock readerWriterLock) : base(readerWriterLock.AcquireReaderLock, readerWriterLock.ReleaseReaderLock, -1)
        {
        }

        /// <summary>
        /// 	Tries to acquire a reader lock on the  readerWriterLock received 
        /// 	with the timeout specified.
        /// </summary>
        public ReaderLock(ReaderWriterLock readerWriterLock, int millisecondsTimeout) : base(readerWriterLock.AcquireReaderLock, readerWriterLock.ReleaseReaderLock, millisecondsTimeout)
        {
        }

        /// <summary>
        /// 	Tries to acquire a reader lock on the readerWriterLock received 
        /// 	with the timeout specified.
        /// </summary>
        public ReaderLock(ReaderWriterLock readerWriterLock, TimeSpan timeout) : base(readerWriterLock.AcquireReaderLock, readerWriterLock.ReleaseReaderLock, timeout)
        {
        }

        #endregion
    }
}